import { API, IMAGE_API } from '@/config';
import Taro from '@tarojs/taro';

/**
 * toast
 * @param title - 显示内容，默认操作成功
 * @param icon - 显示图标'success' | 'error' | 'loading' | 'none'，默认不显示none
 * @param duration - 持续时间，单位毫秒，默认2秒
 */
export const toast = (
  title?: string,
  icon?: 'success' | 'error' | 'loading' | 'none',
  duration?: number,
) => {
  if (!title) title = '操作成功';
  if (!icon) icon = 'none';
  if (!duration) duration = 2000;
  Taro.showToast({
    title,
    icon,
    duration,
  });
};

/**
 * 验证是否是邮箱地址
 * @param email - 邮箱地址
 * @returns boolean
 */
export function isValidEmail(email: string): boolean {
  const emailRegex = /^[^\s@]+@[^\s@]+\.[^\s@]+$/;
  return emailRegex.test(email);
}

/**
 * 验证是否是手机号码
 * @param phone - 手机号码
 * @returns boolean
 */
export function isValidPhone(phone: string): boolean {
  const phoneRegex = /^1[3-9][0-9]{9}$/;
  return phoneRegex.test(phone);
}

/**
 * 生成uuid
 * @returns 返回uuid字符串
 */
export function uuid() {
  return 'xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx'.replace(/[xy]/g, function (c) {
    var r = (Math.random() * 16) | 0,
      v = c == 'x' ? r : (r & 0x3) | 0x8;
    return v.toString(16);
  });
}

/**
 * 后端返回字符串转换成列表
 * @param str - 后端的字符串
 * @returns 返回以[,;，；]分割的列表
 */
export function strToArray(str: string): Array<string> {
  return str
    .split(/[,;，；]+/)
    .map(item => item.trim())
    .filter(item => item !== '');
}

/**
 * 选择本地图片
 * @param count - 可以多选几个，默认1个（不能多选）
 * @returns 返回图片列表或图片地址，promise返回
 */
export function chooseImg(count = 1): Promise<string | Array<string>> {
  return new Promise((resolve, reject) => {
    Taro.chooseImage({
      count,
      sourceType: ['album', 'camera'],
      success: res => {
        if (count == 1) resolve(res.tempFilePaths[0]);
        else resolve(res.tempFilePaths);
      },
      fail: reject,
    });
  });
}

/**
 * 复制字符串到粘贴板
 * @param str - 字符串
 */
export function copy(str: string | number | null | undefined) {
  const data = str + '';
  if (!data) {
    toast('内容为空', 'error');
    return Promise.resolve(null);
  }
  Taro.setClipboardData({ data })
    .then(() => toast('复制成功'))
    .catch(() => toast('复制失败', 'error'));
}

/**
 * 统一给图片加上前缀
 * @param url - 图片地址，可以是有前缀和没前缀的
 * @param prefix - 图片前缀，默认是当前服务器地址
 * @returns 完整图片地址
 */
export function imgAddPrefix(url: string, prefix: string = IMAGE_API): string {
  const res = url.startsWith('http') ? url : prefix + url;
  return res;
}

/**
 * 保存图片到相机
 * @param filePath - 图片地址，只能是网络地址
 */
export function saveImageToAlbum(filePath: string) {
  Taro.saveImageToPhotosAlbum({
    filePath,
  })
    .then(() => toast('保存成功'))
    .catch(() => toast('保存失败', 'error'));
}

/**
 * 判断性别
 * @param gender - 性别代码，0: 男, 1: 女, 3: 未知，可以是数字或字符串
 * @returns 性别字符串
 */
export function getGender(gender: number | string): string {
  const genderCode = typeof gender === 'string' ? parseInt(gender, 10) : gender;
  switch (genderCode) {
    case 0:
      return '男';
    case 1:
      return '女';
    case 3:
      return '未知';
    default:
      return '未知';
  }
}

/**
 * 给数字类型增加单位，例如1600转换成1.6k
 * @param num - 想要转换的数字
 * @returns 增加单位后的数字，如1.6k
 */
export function addUnits(num: number | string): string {
  const unit = typeof num === 'string' ? parseInt(num, 10) : num;

  if (unit >= 100000) {
    // 大于等于 100000 使用 'w' 单位
    return (unit / 10000).toFixed(1) + 'w';
  } else if (unit >= 10000) {
    // 大于等于 10000 使用 'w' 单位
    return (unit / 10000).toFixed(1) + 'w';
  } else if (unit >= 1000) {
    // 大于等于 1000 使用 'k' 单位
    return (unit / 1000).toFixed(1) + 'k';
  } else {
    // 小于 1000 不使用单位
    return unit.toString();
  }
}

/**
 * 格式化手机号或邮箱
 * @param contact - 手机号或邮箱
 * @returns 格式化后的字符串
 */
export function formatContact(contact: string): string {
  if (isValidPhone(contact)) {
    return contact.replace(/^(\d{3})\d{4}(\d{4})$/, '$1****$2');
  } else if (isValidEmail(contact)) {
    const [localPart, domain] = contact.split('@');
    if (localPart.length > 3) {
      return `${localPart.slice(0, 3)}****@${domain}`;
    } else {
      return `${localPart}****@${domain}`;
    }
  } else return contact;
}

/**
 * 将时间（以秒为单位）格式化为 mm:ss 格式的字符串
 *
 * @param time - 以秒为单位的时间
 * @returns 格式化后的时间字符串，格式为 mm:ss
 */
export const formatTime = (time: number): string => {
  const minutes = Math.floor(time / 60);
  const seconds = Math.floor(time % 60);
  return `${String(minutes).padStart(2, '0')}:${String(seconds).padStart(
    2,
    '0',
  )}`;
};
